package shiyl.use.springboot.requestparam.controller;

import lombok.extern.slf4j.Slf4j;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.web.bind.annotation.*;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

import static java.lang.String.format;
import static shiyl.use.springboot.requestparam.controller.ControllerHelper.createResponseMap;

/**
 * <pre>
 * 演示<code>@PathVariable</code>的使用
 * <code>@PathVariable</code>，将URL中的占位符参数绑定到控制器处理方法的入参，即url/{param}这种形式。
 * <code>@pathVariable</code>，是按照value(name)属性进行解析匹配，和URL参数的顺序是无关。
 * <code>@PathVariable</code>参数接收类型使用基本类型，如：int，long，Date，String等，Spring能根据URL变量的具体值以及函数参数的类型来进行转换。
 * <code>@PathVariable</code>可以定义正则表达式进行更精确的控制，定义语法是{变量名：正则表达式}[a-zA-Z0-9_]+是一个正则表达式，表示只能包含小写字母，大写字母，数字，下划线。如此设置URL变量规则后，不合法的URL则不会被处理，直接由SpringMVC框架返回404Not Found。
 * </pre>
 *
 * @author shiyl
 */
@Slf4j
@RestController
@RequestMapping(value = "/pathvariable")
public class PathVariableDemoController {

    /**
     * GET /pathvariable/{key}/{seq}
     *
     * @param key
     * @param seq
     * @return 以Map方式返回，不会有中文乱码
     */
    @GetMapping("/demo1/{key}/{seq}")
    public Map<String, String> demo1(@PathVariable String key, @PathVariable String seq) {
        Map<String, String> back = createResponseMap();
        back.put("key", key);
        back.put("seq", seq);
        return back;
    }

    /**
     * GET /pathvariable/{keyName}
     *
     * @param key
     * @return
     */
    @GetMapping(value = "/demo2/{keyName}")
    public Map<String, String> demo2(@PathVariable("keyName") String key) {
        Map<String, String> back = createResponseMap();
        back.put("key", key);
        return back;
    }

    /**
     * GET /pathvariable/demo3/{keyName}
     *
     * @param key 必输
     * @return
     */
    @GetMapping(value = "/demo3/{keyName}")
    public Map<String, String> demo3(@PathVariable(value = "keyName", required = true) String key) {
        Map<String, String> back = createResponseMap();
        back.put("key", key);
        return back;
    }

    /**
     * GET /pathvariable/demo4/{keyName}/{password}
     *
     * @param key
     * @return 字符串(返回字符串中的中文会乱码)
     */
    @GetMapping(value = "/demo4/{keyName}/{password}")
    public String demo4(@PathVariable(value = "keyName") String key, @PathVariable String password) {
        String backStr = format("收到参数 keyName as key =%s , password = %s ", key, password);
        return backStr;
    }

    /**
     * <pre>
     * GET /pathvariable/demo5/{keyName}/{password}
     * produces 指定了传输格式和字符编码，解决返回String中中文乱码
     * </pre>
     * @param key
     * @return 字符串
     */
    @GetMapping(value = "/demo5/{keyName}/{password}", produces = {"application/json;charset=UTF-8"})
    public String demo5(@PathVariable(value = "keyName") String key, @PathVariable String password) {
        String backStr = format("收到参数 keyName as key =%s , password = %s ", key, password);
        return backStr;
    }


    @PostMapping(value = "/demo6/{user}/{pwd}")
    public Map<String, String> demo6(@PathVariable("user") String userName, @PathVariable("pwd") String password) {
        Map back = createResponseMap();
        back.put("user", userName);
        back.put("pwd", password);
        return back;
    }

    @PostMapping(value = "/demo62/{user}/{pwd}")
    public String demo62(@PathVariable("user") String userName, @PathVariable("pwd") String password) {
        Map back = createResponseMap();
        back.put("user", userName);
        back.put("pwd", password);
        return back.toString() ;
    }

    @PutMapping(value = "/demo7/{user}/{pwd}")
    public Map<String, String> demo7(@PathVariable("user") String userName, @PathVariable("pwd") String password) {
        Map back = createResponseMap();
        back.put("user", userName);
        back.put("pwd", password);
        return back;
    }

    @DeleteMapping(value = "/demo8/{user}/{pwd}")
    public Map<String, String> demo8(@PathVariable("user") String userName, @PathVariable("pwd") String password) {
        Map back = createResponseMap();
        back.put("user", userName);
        back.put("pwd", password);
        return back;
    }

    @GetMapping("/demo9/{username:[a-zA-Z0-9_]+}/blog/{blogId}")
    public Map<String,String> demo9(@PathVariable String username, @PathVariable String blogId){
        Map back = createResponseMap();
        back.put("username", username);
        back.put("blogId", blogId);
        return back;
    }

    /**
     * 要求sex必须是F(Female)或者M(Male)，那么我们的URL模板可以定义为/sex/{sex:M|F}
     * @param sex 性别，传 M或F
     * @return
     */
    @GetMapping("/demo92/{sex:F|M}")
    public Map<String,String> demo92(@PathVariable String sex){
        Map back = createResponseMap();
        back.put("sex", sex);
        return back;
    }

    /**
     * 通过<code>@PathVariable</code>获取URL中的日期类型
     * @param birthDay yyyy-MM-dd
     * @param timeStamp yyyyMMddHHmmssSSS
     * @return
     */
    @GetMapping("/demo10/{birthDay}/{timeStamp}")
    public Map<String,String> demo10(
            @PathVariable @DateTimeFormat(pattern = "yyyy-MM-dd") Date birthDay,
            @PathVariable @DateTimeFormat(pattern = "yyyyMMddHHmmssSSS") Date timeStamp){

        Map<String,String> back = createResponseMap() ;
        if( null != birthDay ){
            String date = new SimpleDateFormat("yyyy-MM-dd").format(birthDay) ;
            log.info("%s", date);
            back.put("birthDay",date);
        }

        if( null != timeStamp ){
            String timestamp = new SimpleDateFormat("yyyyMMddHHmmssSSS").format(timeStamp );
            log.info("%s", timestamp);
            back.put("timeStamp", timestamp);
        }

        return back;
    }

}
